package user

import (
	"context"
	"encoding/json"
	"fmt"
	"github.com/gin-gonic/gin"
	"math/rand"
	"net/http"
	"shangyuapi/data_source"
	"shangyuapi/models"
	"shangyuapi/service"
	"shangyuapi/utils"
	"strings"
	"time"
)

type UserinfoBody struct {
	Uid      int64  `json:"uid" gorm:"uid"`
	Nickname string `json:"nickname" gorm:"nickname"`
	Phone    string `json:"phone" gorm:"phone"`
	Pwd      string `json:"pwd" gorm:"pwd"`
	Logo     string `json:"logo" gorm:"logo"`
	Images   string `json:"images" gorm:"images"`
	Xuehao   string `json:"xuehao" gorm:"xuehao"` // 学号
	Ruxue    string `json:"ruxue" gorm:"ruxue"`   // 入学时间
	Pid      int64  `json:"pid" gorm:"pid"`       // 上级id
	City     string `json:"city" gorm:"city"`     // 城市
	Cityid   int64  `json:"cityid" gorm:"cityid"` // 城市

	Sex       int64   `json:"sex" gorm:"sex"`             // 1男 2女
	Shengri   string  `json:"shengri" gorm:"shengri"`     // 生日
	Name      string  `json:"name" gorm:"name"`           // 姓名
	Xingzuo   string  `json:"xingzuo" gorm:"xingzuo"`     // 星座
	Height    float64 `json:"height" gorm:"height"`       // 身高
	Weight    float64 `json:"weight" gorm:"weight"`       // 体重
	Career    string  `json:"career" gorm:"career"`       // 职业
	Company   string  `json:"company" gorm:"company"`     // 工作单位
	Income    string  `json:"income" gorm:"income"`       // 收入
	Education string  `json:"education" gorm:"education"` // 学历
	School    string  `json:"school" gorm:"school"`       // 毕业院校
	Weixin    string  `json:"weixin" gorm:"weixin"`       // 微信号

	Nationality string `json:"nationality" gorm:"nationality"` // 民族
	Huji        string `json:"huji" gorm:"huji"`               // 户籍
	Children    string `json:"children" gorm:"children"`       // 子女情况
	Marriage    string `json:"marriage" gorm:"marriage"`       // 婚姻情况
	Belief      string `json:"belief" gorm:"belief"`           // 信仰
	Smoke       string `json:"smoke" gorm:"smoke"`             // 烟
	Wine        string `json:"wine" gorm:"wine"`               // 酒
	Agemax      int64  `json:"agemax" gorm:"agemax"`           //交友最大年龄
	Agemin      int64  `json:"agemin" gorm:"agemin"`           //交友最小年龄

	Biaoqian string `json:"biaoqian" gorm:"biaoqian"` // 标签逗号拼接
	Title    string `json:"title" gorm:"title"`       // 自我描述
	Family   string `json:"family" gorm:"family"`     // 家庭描述
	Love     string `json:"love" gorm:"love"`         // 向往的爱情描述

	Cardid        string `json:"cardid" gorm:"cardid"`       // 身份证号
	Cardfront     string `json:"cardfront" gorm:"cardfront"` // 身份证正面
	Cardback      string `json:"cardback" gorm:"cardback"`   // 身份证反面
	Fangchangcity string `json:"fangchangcity" gorm:"fangchangcity"`
	Fangchanimage string `json:"fangchanimage" gorm:"fangchanimage"`
	Cartimage     string `json:"cartimage" gorm:"cartimage"`
}
type UsertjRBody struct {
	Tjnum      int64 `json:"tjnum" gorm:"tjnum"`
	Hdxingbi   int64 `json:"hdxingbi" gorm:"hdxingbi"`
	Jjhdxingbi int64 `json:"jjhdxingbi" gorm:"jjhdxingbi"`
}

func Usertj(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	var user []models.User
	data_source.Db.Where("pid = ?", uid).Find(&user)
	var tjnum int64
	var hdxingbi int64
	var jjhdxingbi int64

	for _, v := range user {
		tjnum = tjnum + 1
		if v.Shoucong == 0 {
			jjhdxingbi = jjhdxingbi + 1
		} else {
			hdxingbi = hdxingbi + 1
		}
	}
	hdxingbi = hdxingbi * 20
	jjhdxingbi = jjhdxingbi * 20
	data := UsertjRBody{
		Tjnum:      tjnum,
		Hdxingbi:   hdxingbi,
		Jjhdxingbi: jjhdxingbi,
	}
	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    data,
		"msg":     "ok",
	})
	return
}
func Userzlrz(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	cardid := request.Cardid
	cardfront := request.Cardfront
	cardback := request.Cardback
	fangchangcity := request.Fangchangcity
	fangchanimage := request.Fangchanimage
	cartimage := request.Cartimage

	var miyao string
	miyao = service.Miyao()
	key := []byte(miyao)
	cardidjm, _ := service.Encrypt(key, cardid)

	user := models.User{
		Cardid:        cardidjm,
		Cardfront:     cardfront,
		Cardback:      cardback,
		Fangchangcity: fangchangcity,
		Fangchanimage: fangchanimage,
		Cartimage:     cartimage,
		Zlrz:          2,
	}

	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}

func Usershenhe(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid

	user := models.User{
		Shenhe: 2,
	}

	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}

func Usermiaoshu(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	title := request.Title
	family := request.Family
	love := request.Love
	user := models.User{
		Title:  title,
		Family: family,
		Love:   love,
		Grms:   2,
	}

	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func Userbiaoqian(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	biaoqian := request.Biaoqian
	user := models.User{
		Biaoqian: biaoqian,
		Grbq:     2,
	}

	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func Userjybz(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	agemax := request.Agemax
	agemin := request.Agemin
	user := models.User{
		Agemax: agemax,
		Agemin: agemin,
		Jybz:   2,
	}

	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func Userxxzl(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	nationality := request.Nationality
	huji := request.Huji
	children := request.Children
	marriage := request.Marriage
	belief := request.Belief
	smoke := request.Smoke
	wine := request.Wine

	if nationality != "" && huji != "" && children != "" && marriage != "" && belief != "" && smoke != "" && wine != "" {
		user := models.User{
			Nationality:  nationality,
			Huji:         huji,
			Children:     children,
			Marriage:     marriage,
			Belief:       belief,
			Smoke:        smoke,
			Wine:         wine,
			Xingxiziliao: 2,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	} else {
		user := models.User{
			Nationality:  nationality,
			Huji:         huji,
			Children:     children,
			Marriage:     marriage,
			Belief:       belief,
			Smoke:        smoke,
			Wine:         wine,
			Xingxiziliao: 1,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	}

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func Userjbxc(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	sex := request.Sex
	shengri := request.Shengri
	name := request.Name
	xingzuo := request.Xingzuo
	height := request.Height
	weight := request.Weight
	career := request.Career
	company := request.Company
	income := request.Income
	education := request.Education
	city := request.City
	cityid := request.Cityid
	school := request.School
	weixin := request.Weixin

	if sex != 0 && shengri != "" && name != "" && xingzuo != "" && height > 0 && weight > 0 && career != "" && company != "" && income != "" && education != "" && cityid > 0 && city != "" && school != "" && weixin != "" {
		user := models.User{
			Sex:         sex,
			Shengri:     shengri,
			Name:        name,
			Xingzuo:     xingzuo,
			Height:      height,
			Weight:      weight,
			Career:      career,
			Company:     company,
			Income:      income,
			Education:   education,
			Cityid:      cityid,
			City:        city,
			School:      school,
			Weixin:      weixin,
			Jichuziliao: 2,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	} else {
		user := models.User{
			Sex:         sex,
			Shengri:     shengri,
			Name:        name,
			Xingzuo:     xingzuo,
			Height:      height,
			Weight:      weight,
			Career:      career,
			Company:     company,
			Income:      income,
			Education:   education,
			Cityid:      cityid,
			City:        city,
			School:      school,
			Weixin:      weixin,
			Jichuziliao: 1,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	}

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func Userupdate(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	nickname := request.Nickname
	logo := request.Logo
	sex := request.Sex
	shengri := request.Shengri
	city := request.City
	cityid := request.Cityid
	pid := request.Pid
	age := calculateAge(shengri)
	user := models.User{
		Nickname: nickname,
		Shengri:  shengri,
		Logo:     logo,
		Sex:      sex,
		City:     city,
		Cityid:   cityid,
		Pid:      pid,
		Ziliao:   2,
		Age:      int64(age),
	}
	data_source.Db.Where("id = ?", uid).Updates(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}
func calculateAge(birthday string) (age int) {
	layout := "2006-01-02"
	t, _ := time.Parse(layout, birthday)
	now := time.Now()
	age = now.Year() - t.Year()
	if now.AddDate(-age, 0, 0).Before(t) {
		age--
	}
	return age
}
func Userxiangce(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	images := request.Images
	imagearr := strings.Split(images, ",")
	if len(imagearr) < 4 {
		user := models.User{
			Images:  images,
			Xiangce: 1,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	} else {
		user := models.User{
			Images:  images,
			Xiangce: 2,
		}

		data_source.Db.Where("id = ?", uid).Updates(&user)
	}

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}

func Userinfo(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	//tokenval := ctx.Request.Header.Get("x-token")
	//// 将uid取出context
	//uid, ok := ctx.Get(tokenval)
	//if !ok {
	//	fmt.Println(ok)
	//	return
	//}
	var user models.User
	data_source.Db.Where("id = ?", uid).First(&user)
	if user.Phone != "" {
		var miyao string
		miyao = service.Miyao()
		key := []byte(miyao)
		//fmt.Println(miyao)
		phone, _ := service.Decrypt(key, user.Phone)
		//fmt.Println(phone)
		user.Phone = phone
	}
	//data_source.Db.Model(&models.User{}).Where("id = ?", uid).Update("updatetime", time.Now().Unix())

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    user,
		"msg":     "ok",
	})
	return
}

func Usertoken(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	var user models.User
	data_source.Db.Where("id = ?", uid).First(&user)
	if user.ID == 0 {
		ctx.JSON(http.StatusOK, gin.H{
			"code":    400,
			"error":   1,
			"success": 0,
			"data":    "用户不存在",
			"msg":     "no",
		})
		return
	}
	mySigninkkey := []byte("woshiyanwei199511111")
	token, err := utils.GenToken(uid, time.Duration(86400)*time.Second, mySigninkkey)
	if err != nil {
		fmt.Println(err)
	}
	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    token,
		"msg":     "ok",
	})
	return
}
func Userimages(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	uid := request.Uid
	var user models.Userimg
	data_source.Db.Model(&models.User{}).Where("id = ?", uid).First(&user)

	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    user,
		"msg":     "ok",
	})
	return
}

type PhonecodeBody struct {
	Phone string `json:"phone" from:"phone"`
}

func Phonecode(ctx *gin.Context) {
	request := PhonecodeBody{}
	ctx.ShouldBind(&request)
	phone := request.Phone
	phone = strings.Replace(phone, " ", "", -1)
	rnd := rand.New(rand.NewSource(time.Now().UnixNano()))
	vcode := fmt.Sprintf("%06v", rnd.Int31n(1000000))

	par, _ := json.Marshal(map[string]interface{}{
		"code": vcode,
	})
	_, err := SendSms("LTAI4FiQxh84Qy2hNQKU28P2", "TD5vAh2o4lVTse04cKhsG7d8qtmtJK", "嘉医良方", phone, "SMS_468965512", string(par))
	fmt.Println(err)
	if err == nil {
		phonecode := models.Phonecode{
			Phone:   phone,
			Code:    vcode,
			Enttime: time.Now().Unix() + 900,
		}
		data_source.Db.Create(&phonecode)
	} else {
		ctx.JSON(http.StatusOK, gin.H{
			"code":    400,
			"error":   1,
			"success": 400,
			"data":    "on",
			"msg":     err,
		})
		return
	}
	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    "ok",
		"msg":     "ok",
	})
	return
}

func Ceshi(ctx *gin.Context) {
	request := UserinfoBody{}
	ctx.ShouldBind(&request)
	phone := request.Phone
	var miyao string
	miyao = "123456789012345shanyuyanweikaifa"
	fmt.Println(miyao)
	key := []byte(miyao)

	jiami, err := service.Encrypt(key, phone)
	jiemi, err := service.Decrypt(key, jiami)
	if err != nil {
		fmt.Println(err)
	}
	ctx.JSON(http.StatusOK, gin.H{
		"code":    0,
		"error":   0,
		"success": 200,
		"data":    jiami,
		"data1":   jiemi,
		"msg":     "ok",
	})
	return
}

type key int64

const uidKey key = 0

// GetUIDFromContext 从 context 中获取 uid
func GetUIDFromContext(ctx context.Context) (string, bool) {
	uid, ok := ctx.Value(uidKey).(string)
	return uid, ok
}
